import numpy as np
from scipy.optimize import curve_fit
import matplotlib.pyplot as plt

# 定义半个周期正弦函数
def half_sine(x, A, w, phi, c):
    return A * np.sin(w * x + phi) + c

# 假设这是您的数据
data1 = np.array([
    [43, 295],
    [42, 294],
    [42, 291],
    [42, 288],
    [42, 286],
    [42, 282],
    [43, 277],
    [45, 270],
    [45, 266],
    [47, 260],
    [48, 248],
    [49, 239],
    [50, 232],
    [51, 225],
    [53, 217],
    [57, 207],
    [59, 205],
    [62, 199],
    [65, 196],
    [68, 192],
    [72, 188],
    [72, 186],
    [76, 183],
    [80, 179],
    [84, 174],
    [88, 170],
    [93, 166],
    [98, 162],
    [103, 158],
    [108, 153],
    [112, 150],
    [117, 146],
    [122, 142],
    [128, 138],
    [132, 136],
    [136, 133],
    [144, 129],
    [148, 126],
    [153, 123],
    [158, 121],
    [161, 119],
    [164, 118],
    [168, 117],
    [168, 116],
    [171, 115],
    [173, 114],
    [176, 114],
    [177, 113],
    [180, 112],
    [182, 111],
    [184, 111],
    [186, 111],
    [189, 111],
    [192, 111],
    [195, 111],
    [198, 111],
    [201, 111],
    [206, 111],
    [213, 111],
    [217, 111],
    [223, 111],
    [228, 111],
    [233, 111],
    [238, 112],
    [239, 112],
    [241, 113],
    [243, 114],
    [243, 115],
    [244, 116],
    [246, 117],
    [248, 118],
    [250, 120],
    [252, 122],
    [256, 125],
    [260, 130],
    [263, 134],
    [268, 138],
    [272, 145],
    [276, 148],
    [280, 154],
    [288, 163],
    [293, 170],
    [300, 180],
    [308, 190],
    [316, 202],
    [321, 210],
    [324, 214],
    [332, 225],
    [334, 230],
    [337, 235],
    [340, 240],
    [341, 242],
    [344, 246],
    [346, 250],
    [348, 254],
    [350, 259],
    [353, 264],
    [355, 267],
    [356, 271],
    [357, 274],
    [358, 277],
    [360, 280],
    [360, 282],
    [361, 283],
    [361, 284],
    [362, 286],
    [362, 286],
    [362, 287],
    [362, 286]
])
data2=np.array(
[[  7 ,910],
 [  7 ,909],
 [  7 ,908],
 [  7 ,906],
 [  8 ,904],
 [  9 ,902],
 [ 11 ,900],
 [ 14 ,896],
 [ 16 ,894],
 [ 17 ,893],
 [ 19 ,891],
 [ 21 ,889],
 [ 25 ,885],
 [ 26 ,884],
 [ 29 ,882],
 [ 33 ,878],
 [ 36 ,875],
 [ 40 ,871],
 [ 41 ,870],
 [ 44 ,869],
 [ 46 ,866],
 [ 48 ,865],
 [ 50 ,863],
 [ 52 ,862],
 [ 54 ,860],
 [ 56 ,859],
 [ 59 ,857],
 [ 63 ,854],
 [ 68 ,851],
 [ 76 ,848],
 [ 80 ,847],
 [ 92 ,844],
 [103 ,842],
 [110 ,841],
 [120 ,838],
 [128 ,838],
 [141 ,835],
 [152 ,833],
 [161 ,832],
 [169 ,831],
 [179 ,830],
 [187 ,829],
 [202 ,826],
 [212 ,826],
 [220 ,826],
 [228 ,826],
 [236 ,826],
 [248 ,826],
 [253 ,826],
 [261 ,826],
 [263 ,826],
 [269 ,826],
 [272 ,826],
 [273 ,826],
 [276 ,826],
 [280 ,826],
 [286 ,826],
 [290 ,826],
 [294 ,826],
 [298 ,826],
 [304 ,826],
 [308 ,827],
 [316 ,828],
 [321 ,830],
 [325 ,830],
 [331 ,831],
 [335 ,832],
 [341 ,834],
 [345 ,834],
 [350 ,837],
 [353 ,838],
 [356 ,838],
 [360 ,840],
 [362 ,841],
 [363 ,841],
 [365 ,842],
 [366 ,842],
 [368 ,844],
 [370 ,845],
 [372 ,846],
 [373 ,846],
 [375 ,848],
 [376 ,849],
 [378 ,850],
 [380 ,852],
 [383 ,854],
 [385 ,856],
 [388 ,858],
 [391 ,860],
 [394 ,863],
 [397 ,866],
 [400 ,868],
 [404 ,871],
 [406 ,872],
 [409 ,875],
 [412 ,878],
 [415 ,882],
 [417 ,884],
 [420 ,886],
 [421 ,888],
 [424 ,890],
 [425 ,892],
 [426 ,894],
 [428 ,896],
 [430 ,897],
 [432 ,899],
 [432 ,901],
 [433 ,902],
 [435 ,905],
 [436 ,906],
 [438 ,906],
 [440 ,909],
 [441 ,911],
 [441 ,913],
 [443 ,914],
 [444 ,914],
 [444 ,915],
 [444 ,915],
 [444 ,917],
 [446 ,919],
 [447 ,921],
 [448 ,922],
 [449 ,924],
 [451 ,926],
 [452 ,929],
 [453 ,930],
 [455 ,933],
 [456 ,934],
 [456 ,935],
 [457 ,936],
 [457 ,937],
 [457 ,938],
 [458 ,938],
 [459 ,938],
 [459 ,939],
 [459 ,940],
 [459 ,941],
 [460 ,941],
 [460 ,942]]
)
data3=np.array(
[[ 51 ,336],
 [ 51 ,335],
 [ 51 ,334],
 [ 51 ,332],
 [ 51 ,331],
 [ 51 ,330],
 [ 51 ,328],
 [ 51 ,326],
 [ 51 ,326],
 [ 51 ,324],
 [ 51 ,322],
 [ 51 ,321],
 [ 52 ,320],
 [ 52 ,319],
 [ 52 ,318],
 [ 52 ,317],
 [ 52 ,316],
 [ 53 ,314],
 [ 53 ,314],
 [ 54 ,313],
 [ 54 ,312],
 [ 54 ,311],
 [ 54 ,310],
 [ 55 ,310],
 [ 55 ,309],
 [ 56 ,307],
 [ 56 ,306],
 [ 56 ,306],
 [ 56 ,304],
 [ 57 ,302],
 [ 57 ,301],
 [ 58 ,300],
 [ 58 ,298],
 [ 59 ,298],
 [ 59 ,296],
 [ 60 ,294],
 [ 60 ,294],
 [ 61 ,290],
 [ 62 ,288],
 [ 62 ,286],
 [ 63 ,285],
 [ 64 ,282],
 [ 65 ,278],
 [ 68 ,274],
 [ 69 ,271],
 [ 70 ,270],
 [ 71 ,266],
 [ 72 ,264],
 [ 72 ,262],
 [ 72 ,260],
 [ 73 ,258],
 [ 74 ,255],
 [ 75 ,253],
 [ 76 ,250],
 [ 76 ,249],
 [ 77 ,246],
 [ 78 ,244],
 [ 79 ,242],
 [ 79 ,242],
 [ 79 ,240],
 [ 80 ,238],
 [ 80 ,238],
 [ 80 ,235],
 [ 81 ,234],
 [ 82 ,232],
 [ 82 ,230],
 [ 83 ,227],
 [ 84 ,224],
 [ 84 ,222],
 [ 86 ,219],
 [ 87 ,218],
 [ 87 ,217],
 [ 88 ,215],
 [ 88 ,214],
 [ 89 ,211],
 [ 90 ,210],
 [ 92 ,207],
 [ 92 ,206],
 [ 93 ,204],
 [ 95 ,202],
 [ 96 ,201],
 [ 96 ,199],
 [ 98 ,197],
 [100 ,194],
 [101 ,192],
 [104 ,190],
 [105 ,188],
 [108 ,184],
 [109 ,183],
 [112 ,181],
 [112 ,178],
 [116 ,176],
 [116 ,174],
 [119 ,172],
 [121 ,170],
 [124 ,168],
 [127 ,166],
 [128 ,165],
 [131 ,163],
 [132 ,162],
 [135 ,159],
 [137 ,158],
 [140 ,156],
 [145 ,154],
 [148 ,152],
 [153 ,150],
 [156 ,149],
 [160 ,147],
 [165 ,146],
 [168 ,145],
 [170 ,145],
 [175 ,143],
 [177 ,143],
 [180 ,142],
 [184 ,142],
 [187 ,142],
 [189 ,142],
 [192 ,142],
 [194 ,142],
 [196 ,142],
 [197 ,142],
 [198 ,142],
 [199 ,142],
 [200 ,143],
 [200 ,144],
 [201 ,144],
 [201 ,145],
 [203 ,145],
 [204 ,146],
 [204 ,147],
 [205 ,148],
 [208 ,150],
 [208 ,151],
 [212 ,155],
 [213 ,157],
 [214 ,159],
 [217 ,162],
 [219 ,166],
 [221 ,170],
 [222 ,172],
 [224 ,174],
 [225 ,177],
 [227 ,181],
 [228 ,182],
 [230 ,186],
 [231 ,188],
 [232 ,190],
 [233 ,193],
 [235 ,196],
 [236 ,200],
 [237 ,204],
 [238 ,205],
 [239 ,208],
 [239 ,210],
 [240 ,213],
 [241 ,214],
 [242 ,217],
 [243 ,219],
 [244 ,222],
 [245 ,226],
 [246 ,230],
 [248 ,233],
 [248 ,236],
 [250 ,239],
 [250 ,241],
 [251 ,243],
 [252 ,245],
 [252 ,246],
 [254 ,250],
 [255 ,252],
 [255 ,254],
 [256 ,256],
 [256 ,258],
 [256 ,261],
 [258 ,264],
 [258 ,266],
 [259 ,268],
 [259 ,270],
 [260 ,272],
 [260 ,274],
 [260 ,276],
 [260 ,278],
 [261 ,278],
 [262 ,282],
 [262 ,282],
 [263 ,284],
 [264 ,285],
 [264 ,286],
 [264 ,286],
 [264 ,287],
 [264 ,288],
 [264 ,289],
 [264 ,290],
 [264 ,290],
 [264 ,291],
 [264 ,292],
 [264 ,293],
 [265 ,294],
 [265 ,294],
 [266 ,296],
 [266 ,298],
 [267 ,299],
 [267 ,300],
 [267 ,301],
 [267 ,302],
 [268 ,303],
 [268 ,304],
 [268 ,305],
 [268 ,306],
 [268 ,306],
 [268 ,307],
 [268 ,308],
 [269 ,309],
 [270 ,310],
 [270 ,310]]
)
data4=np.array(
[[ 87,  73],
 [ 87,  74],
 [ 87,  77],
 [ 87,  79],
 [ 87,  81],
 [ 87,  85],
 [ 87,  93],
 [ 87,  97],
 [ 87, 105],
 [ 87, 110],
 [ 88, 119],
 [ 88, 124],
 [ 89, 131],
 [ 90, 138],
 [ 92, 145],
 [ 94, 151],
 [ 95, 154],
 [ 96, 160],
 [ 97, 166],
 [100, 172],
 [103, 179],
 [104, 186],
 [106, 190],
 [107, 193],
 [108, 196],
 [111, 201],
 [112, 204],
 [114, 209],
 [116, 213],
 [117, 216],
 [119, 220],
 [121, 224],
 [123, 229],
 [124, 234],
 [128, 238],
 [129, 242],
 [131, 245],
 [132, 248],
 [135, 251],
 [136, 254],
 [137, 255],
 [138, 256],
 [138, 257],
 [139, 258],
 [140, 258],
 [140, 258],
 [141, 260],
 [143, 262],
 [145, 263],
 [147, 264],
 [148, 266],
 [151, 268],
 [154, 270],
 [159, 272],
 [164, 274],
 [167, 276],
 [171, 277],
 [176, 278],
 [180, 278],
 [185, 278],
 [189, 278],
 [196, 279],
 [201, 279],
 [209, 279],
 [212, 279],
 [223, 278],
 [225, 278],
 [234, 277],
 [236, 276],
 [245, 274],
 [251, 272],
 [254, 271],
 [262, 268],
 [268, 265],
 [274, 262],
 [279, 260],
 [286, 257],
 [292, 253],
 [300, 247],
 [308, 243],
 [316, 238],
 [321, 235],
 [331, 230],
 [333, 228],
 [340, 222],
 [342, 221],
 [346, 216],
 [348, 214],
 [352, 209],
 [357, 202],
 [359, 199],
 [364, 192],
 [369, 184],
 [374, 176],
 [379, 167],
 [383, 161],
 [387, 156],
 [390, 151],
 [393, 148],
 [394, 146],
 [396, 142],
 [399, 139],
 [400, 137],
 [402, 134],
 [404, 130],
 [406, 127],
 [408, 124],
 [409, 122],
 [412, 117],
 [415, 111],
 [416, 109],
 [418, 105],
 [421, 100],
 [422,  98],
 [422,  97],
 [423,  96],
 [423,  95]]
)

# 每隔5个元素取一个
data = data3[::5]

# 提取x和y数据
x_data = data[:, 0]  # 第一列作为x坐标
y_data = data[:, 1]  # 第二列作为y坐标

# 初始猜测值（A: 振幅, w: 角频率, phi: 相位偏移, c: 垂直偏移）
initial_guess = [np.max(y_data) - np.min(y_data), 2 * np.pi / (x_data[-1] - x_data[0]), 0, np.mean(y_data)]

# 使用 curve_fit 进行拟合，并增加最大迭代次数
params, params_covariance = curve_fit(half_sine, x_data, y_data, p0=initial_guess, maxfev=5000)

# 提取拟合参数
A, w, phi, c = params

# 打印拟合结果
print(f"拟合参数: 振幅(A)={A:.2f}, 角频率(w)={w:.2f}, 相位偏移(phi)={phi:.2f}, 垂直偏移(c)={c:.2f}")

# 生成用于绘图的 x 轴数据
x_fit = np.linspace(x_data.min(), x_data.max(), 1000)
y_fit = half_sine(x_fit, A, w, phi, c)

# 绘制原始数据点
plt.scatter(x_data, y_data, label='Data Points')
# 绘制拟合曲线
plt.plot(x_fit, y_fit, 'r-', label=f'Fit: A={A:.2f}, w={w:.2f}, φ={phi:.2f}, c={c:.2f}')
# 添加图例
plt.legend()
# 设置图表标题和标签
plt.title('Half Sine Curve Fitting')
plt.xlabel('X-axis')
plt.ylabel('Y-axis')
plt.gca().invert_yaxis()
# 显示图形
plt.show()